package com.lf2;


import android.annotation.SuppressLint;
import android.content.Context;

import com.lf2.tool.CharUtil;

import java.io.BufferedWriter;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.io.PrintWriter;
import java.io.StringWriter;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Date;
import java.util.Locale;





/*
Log.d(TAG,new Exception().getStackTrace()[0].getMethodName()); //函数名
Log.d(TAG, Thread.currentThread().getStackTrace()[2].getMethodName()); //函数名
Log.d(TAG, ""+Thread.currentThread().getStackTrace()[2].getLineNumber()); //行号
Log.d(TAG, Thread.currentThread().getStackTrace()[2].getFileName()); //文件名
*/

@SuppressLint("SdCardPath")
public class Lf_Debug
{

  public static String lf_Tag;
  public static String lf_Hex;
  public static String lf_Len;
  public static String lf_Text;
  public static int lf_taglable = 0;
  public static int lf_debugopen=0;
  public static int lf_cardopen=0;
  private static Lf_Debug instance;
  @SuppressLint("SdCardPath")
  private static String MYLOG_PATH_SDCARD_DIR = "/sdcard/logs/";
  private static int SDCARD_LOG_FILE_SAVE_DAYS = 7;
  private static String FILE_NAME = "Log.txt";
  @SuppressLint("SimpleDateFormat")
  private static SimpleDateFormat myLogSdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss.SSS");
  public static int level=0;

  @SuppressLint("SimpleDateFormat")
  private static SimpleDateFormat logfile = new SimpleDateFormat("yyyyMMdd");
  
  public static int DEBUG_LEVEL=0;
  public static int DEBUG_MASK=0;
  public static final int DEBUG_CONNECTION = 1<<31;
  public static final int DEBUG_DATA = 1<<30;
  public static final int DEBUG_ISO = 1<<29;
  
  public static final int DEBUG_UPDATEICCARD = 1<<18;
  public static final int DEBUG_UPDATE = 1<<17;
  public static final int DEBUG_OTHER = 1<<16;
  
  public static final int DEBUG_FUN = 1<<15;
  public static final int DEBUG_PRINTER = 1<<12;
  public static final int DEBUG_BUS = 1<<11;
  public static final int DEBUG_PACKET = 1<<10;
  public static final int DEBUG_EMV = 1<<9;
  public static final int DEBUG_TOOL = 1<<8;
  public static final int DEBUG_TMS = 1<<7;
  public static final int DEBUG_QR = 1<<6;
  public static final int DEBUG_C2B = 1<<5;
  public static final int DEBUG_B2C = 1<<4;
  public static final int DEBUG_BANKCARD = 1<<3;
  public static final int DEBUG_APDU = 1<<2;
  //0和1预留不用
  public static String ftppath="/data/ftp285";
  public static String ftpimei="";
  
  public static int lf_debugtimer=0;
  public static StringBuilder timerBuilder;
  public Lf_Debug() {
	  
  }
  
  public static Lf_Debug getInstance()
  {
     if (instance == null) {
       instance = new Lf_Debug();
    }
    return instance;
  }
  
  public static void dbg_cardopen(int mode){
	  //Log.e("LF_DEBUG", "lf_cardopen : true");
	  lf_cardopen = mode;
  }
  
  public static void dbg_cardopen(){
	  //Log.e("LF_DEBUG", "lf_cardopen : true");
	  lf_cardopen = 1;
  }
  
  public static void dbg_cardclose(){
	  //Log.e("LF_DEBUG", "lf_cardopen : false");
	  lf_cardopen = 0;
  }
  
  public static int dbg_getcard(){
	  //Log.e("LF_DEBUG", "dbg_getcard : "+lf_cardopen);
	  return lf_cardopen;
  }
  
  public static void dbg_open(){
	  lf_debugopen = 1;
  }
  
  public static int dbg_getstatue(){
	  return lf_debugopen;
  }
  
  public static void dbg_open(int mode){
	  lf_debugopen = 1;	  
	  DEBUG_MASK = mode;	 
  }
  
  public static void dbg_close(){
	  lf_debugopen = 0;
  }
  
  public static void dbg_tagset()
  {
	  lf_taglable = 1;
  }
  
  public static void dbg_tagclr()
  {
	  lf_taglable = 0;
  }
  
  public static void dbg_opentimer(){
	  lf_debugtimer = 1;
	  timerBuilder = new StringBuilder();
  }  
  
  public static void dbg_closetimer(){
	  
	  lf_debugtimer = 0;
	  writeLogtoFile("v", "lf_debugtimer", timerBuilder.toString());
  }
  
  public static String _FILE_()
  {   
	  StackTraceElement stackTraces[] = (new Throwable()).getStackTrace();
	  return stackTraces[1].getFileName();   
  }  
  
  public static int _LINE_()   
  {   
	  StackTraceElement stackTraces[] = (new Throwable()).getStackTrace();
	  return stackTraces[1].getLineNumber();   
  }   
  
  public static String _FUNC_()
  {   
	  StackTraceElement stackTraces[] = (new Throwable()).getStackTrace();
	  return stackTraces[1].getMethodName();  
  }   
  
  public static String _TIME_()
  {   
	  Date now = new Date();
	  SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss.SSS", Locale.getDefault());
	  return sdf.format(now);   
  }   
  
  public static String _FILE_LINE_FUNC_()
  {     
  	  DEBUG_LEVEL = 0xffffffff;
	  if(dbg_check() == 0)
	  {
		  return "_FILE_LINE_FUNC_";
	  }
	  StackTraceElement stackTraces[] = (new Throwable()).getStackTrace();
	  StringBuffer strBuffer = new StringBuffer("[");
	  strBuffer.append(stackTraces[1].getFileName()).append("|");    
	  strBuffer.append(stackTraces[1].getLineNumber()).append("|");   
	  strBuffer.append(stackTraces[1].getMethodName()).append("|");   
	  strBuffer.append(Thread.currentThread().getName()).append("]");
	
	  return strBuffer.toString();     
  } 
  
  public static String _FILE_LINE_FUNC_(int flag)
  {     
      DEBUG_LEVEL = flag;
	  if(dbg_check() == 0)
	  {
		  return "_FILE_LINE_FUNC_";
	  }
	  StackTraceElement stackTraces[] = (new Throwable()).getStackTrace();
	  StringBuffer strBuffer = new StringBuffer("[");
	  strBuffer.append(stackTraces[1].getFileName()).append("|");    
	  strBuffer.append(stackTraces[1].getLineNumber()).append("|");    
	  strBuffer.append(stackTraces[1].getMethodName()).append("|");   
	  strBuffer.append(Thread.currentThread().getName()).append("]");

	  return strBuffer.toString();     
  }
  
  public static int dbg_check()
  {	  
	  if(lf_debugopen == 0)
	  {
		  return 0;
	  }
	  if(DEBUG_LEVEL == 1)
	  {
		  return 1;
	  }
	  if(DEBUG_LEVEL != 0xffffffff)
	  {
		  if((DEBUG_LEVEL&DEBUG_MASK) == 0)
		  {			  
			  return 0;
		  }
	  }	  
	  return 1;
  }
  
  public static void dbg_writeStr(byte[] pszText){
	  if(dbg_check() == 0)
	  {
		  return;
	  }
	  lf_Text = printHex(pszText, pszText.length);
	  lflog(level, "LF_Debug", lf_Text);
  }
  
  public static void dbg_writeHex(byte[] pszHex,int HexLen){
	  if(dbg_check() == 0)
	  {
		  return;
	  }
	  lf_Hex = printHex(pszHex, HexLen);
	  lf_Len = String.valueOf(HexLen);
	  lflog(level, "LF_Debug", "[====>长度:"+lf_Len+"]"+lf_Hex); 
  }
  
  public static void dbg_printf(byte[] pszText){
	  if(dbg_check() == 0)
	  {
		  return;
	  }
	  lf_Text = printHex(pszText, pszText.length);
	  lflog(level, "LF_Debug", lf_Text); 
  }
  
  public static void dbg_printfWHex(byte[] pszHex, int HexLen, String pszText){
	  if(dbg_check() == 0)
	  {
		  return;
	  }
	  lf_Hex = printHex(pszHex, HexLen);
	  lf_Len = String.valueOf(HexLen);
	  lf_Text = pszText;
	  lflog(level, "LF_Debug", lf_Text+"[====>长度:"+lf_Len+"]"+lf_Hex); 
	  
  }
  
  public static void dbg_mWriteStr(String mask, String pszText){
	  if(dbg_check() == 0)
	  {
		  return;
	  }
	  if(lf_taglable == 1)
	  {
		  lf_Tag = "LF_Debug";
	  }
	  else
	  {
		  lf_Tag = mask;
	  }
	  lf_Text = pszText;
	  lflog(level, lf_Tag, lf_Text); 
  }
  
  public static void dbg_mWriteHex(String mask, byte[] pszHex, int HexLen){
	  if(dbg_check() == 0)
	  {
		  return;
	  }
	  if(lf_taglable == 1)
	  {
		  lf_Tag = "LF_Debug";
	  }
	  else
	  {
		  lf_Tag = mask;
	  }
	  lf_Hex = printHex(pszHex, HexLen);
	  lf_Len = String.valueOf(HexLen);
	  lflog(level, lf_Tag, "[====>长度:"+lf_Len+"]"+lf_Hex); 
  }
  
  public static void dbg_mPrintf(String mask, String pszText){
	  if(dbg_check() == 0)
	  {
		  return;
	  }
	  if(lf_taglable == 1)
	  {
		  lf_Tag = "LF_Debug";
	  }
	  else
	  {
		  lf_Tag = mask;
	  }
	  lf_Text = pszText;
	  lflog(level, lf_Tag, lf_Text); 
  }
  
  public static void dbg_mPrintf(String mask, String format, Object... args){
	  if(dbg_check() == 0)
	  {
		  return;
	  }
	  String logstr;
      logstr = String.format(format, args);
      if(lf_taglable == 1)
	  {
		  lf_Tag = "LF_Debug";
	  }
	  else
	  {
		  lf_Tag = mask;
	  }
	  lf_Text = logstr;
	  lflog(level, lf_Tag, lf_Text); 
  }
  
  public static void dbg_mPrintfWHex(String mask, byte[] pszHex, int HexLen, String pszText){
	  if(dbg_check() == 0)
	  {
		  return;
	  }
	  if(lf_taglable == 1)
	  {
		  lf_Tag = "LF_Debug";
	  }
	  else
	  {
		  lf_Tag = mask;
	  }
	  lf_Hex = printHex(pszHex, HexLen);
	  lf_Len = String.valueOf(HexLen);
	  lf_Text = pszText;
	  lflog(level, lf_Tag, lf_Text+"[====>len:"+lf_Len+"]"+lf_Hex); 
  }
  
  public static void dbg_mPrintfWHex(String mask, char[] pszHex, int HexLen, String pszText){
	  if(dbg_check() == 0)
	  {
		  return;
	  }
	  if(lf_taglable == 1)
	  {
		  lf_Tag = "LF_Debug";
	  }
	  else
	  {
		  lf_Tag = mask;
	  }
	  lf_Hex = printHex(CharUtil.getBytes(pszHex), HexLen);
	  lf_Len = String.valueOf(HexLen);
	  lf_Text = pszText;
	  lflog(level, lf_Tag, lf_Text+"[====>len:"+lf_Len+"]"+lf_Hex); 
  }
  
  public static void dbg_mPrintfWHex(String mask, char[] pszHex, int HexLen, int mode, String pszText){
	  if(dbg_check() == 0)
	  {
		  return;
	  }
	  if(lf_taglable == 1)
	  {
		  lf_Tag = "LF_Debug";
	  }
	  else
	  {
		  lf_Tag = mask;
	  }
	  lf_Hex = printHex(pszHex, HexLen, mode);
	  lf_Len = String.valueOf(HexLen);
	  lf_Text = pszText;
	  lflog(level, lf_Tag, lf_Text+"[====>len:"+lf_Len+"]"+lf_Hex); 
  }
  
  public static void dbg_mPrintfWHex(String mask, byte[] pszHex, int HexLen, String format, Object... args){
	  if(dbg_check() == 0)
	  {
		  return;
	  }
	  String logstr;
      logstr = String.format(format, args);
      if(lf_taglable == 1)
	  {
		  lf_Tag = "LF_Debug";
	  }
	  else
	  {
		  lf_Tag = mask;
	  }
	  lf_Hex = printHex(pszHex, HexLen);
	  lf_Len = String.valueOf(HexLen);
	  lf_Text = logstr;
	  lflog(level, lf_Tag, lf_Text+"[====>len:"+lf_Len+"]"+lf_Hex); 
  }
  
  private static void lflog(int level, String tag, String msg)
  {
	  if(lf_debugtimer == 1)
	  {
		  Date nowtime = new Date();
		  
		  StringBuilder sb = new StringBuilder();
	      sb.append("\r\n[");
		  sb.append(myLogSdf.format(nowtime));
		  sb.append("-");
		  sb.append(level);
		  sb.append("] ");
		  sb.append(tag);
		  sb.append("/");
	      sb.append(msg);
		  timerBuilder.append(sb.toString());
		  return;
	  }
	  
      if (level >= 0) 
      {
          writeLogtoFile(getLevelName(level), tag, msg);
          {
              switch (level) {
              case 0: 
              	android.util.Log.v(tag, msg);
              break;
              case 1: 
              	android.util.Log.d(tag, msg);
              break;
              case 2: 
              	android.util.Log.i(tag, msg);
              break;
              case 3: 
              	android.util.Log.w(tag, msg);
              break;
              case 4: 
              	android.util.Log.e(tag, msg);
              break;
              }
        
          }
      }      
  }
  
  private static String getLevelName(int level)
  {
      switch (level) 
      {
          case 1: 
            return "D";
		  case 4: 
		    return "E";
		  case 5: 
		    return "F";
		  case 2: 
		    return "I";
		  case 0: 
		    return "V";
		  case 3: 
		    return "W";
	   }
	   return "";
  }
  
  private static synchronized void writeLogtoFile(String level, String tag, String msg)
  {
      Date nowtime = new Date();
      String fileName = logfile.format(nowtime) + FILE_NAME;

      StringBuilder sb = new StringBuilder();
      sb.append("\r\n[");
	  sb.append(myLogSdf.format(nowtime));
	  sb.append("-");
	  sb.append(level);
	  sb.append("] ");
	  sb.append(tag);
	  sb.append("/");
      sb.append(msg);

      String writeMsg = sb.toString();
      
      File file = new File(MYLOG_PATH_SDCARD_DIR);
      if (!file.exists()) {
          file.mkdir();
      }
      file = new File(MYLOG_PATH_SDCARD_DIR, fileName);
      try {
          FileWriter filerWriter = new FileWriter(file, true);
          BufferedWriter bufWriter = new BufferedWriter(filerWriter);
          bufWriter.write(writeMsg);
          bufWriter.newLine();
          bufWriter.close();
          filerWriter.close();
      }
      catch (IOException e)
      {
          e.printStackTrace();
      }
  }
  private static String printHex(byte[] bytes, int HexLen)
  {
      if (bytes == null) {
          return "no data";
      }
	  StringBuilder sBuilder = new StringBuilder();
	  sBuilder.append(" \r\n");
	  for (int i = 0; i < HexLen; i++) {
	      if (i % 16 == 0) {
	          //sBuilder.append("\r\n");
	      }
	      sBuilder.append(String.format("%02X ", bytes[i]));
	  }
      return sBuilder.toString();
  }
  
  private static String printHex(char[] bytes, int HexLen, int mode)
  {
      if (bytes == null) {
          return "no data";
      }
	  StringBuilder sBuilder = new StringBuilder();
	  sBuilder.append(" \r\n");
	  for (int i = 0; i < HexLen; i++) {
	      if (i % 16 == 0 && i != 0) {
	    	  if(mode>0)
	    	  {
	    		  sBuilder.append("\r\n");
	    	  }
	      }
	      if(mode == 1)
	      {
	    	  sBuilder.append(String.format("%04X ", (int)bytes[i]));
	      }
	      else
	      {
	    	  sBuilder.append(String.format("%02X ", (int)bytes[i]));
	      }
	  }
      return sBuilder.toString();
  }
  
  public static void e_printf(String mask, Exception e)
  {
      StringWriter sw = new StringWriter();
      e.printStackTrace(new PrintWriter(sw, true));
      String str = sw.toString();
      dbg_mPrintf(mask, str);
  }
  
  private static void delFile()
  {
      String needDelFiel = logfile.format(getDateBefore());
      File file = new File(MYLOG_PATH_SDCARD_DIR, needDelFiel + FILE_NAME);
      android.util.Log.v("LF_Debug", "删除:"+needDelFiel+FILE_NAME);
      if (file.exists()) 
      {
      	 file.delete();
      }
  }

  private static Date getDateBefore()
  {
      Date nowtime = new Date();
      Calendar now = Calendar.getInstance();
      now.setTime(nowtime);
      now.set(5, now.get(5) - SDCARD_LOG_FILE_SAVE_DAYS);
      return now.getTime();
  }
  
  private static Date getDateCurrent()
  {
      Date nowtime = new Date();
      Calendar now = Calendar.getInstance();
      now.setTime(nowtime);
      now.set(5, now.get(5));
      return now.getTime();
  }
  
  public static void dbg_delfile() {
	 // TODO Auto-generated method stub
	 delFile();
  }
  
  public static void dbg_delallfile() {
	 // TODO Auto-generated method stub
	 File sdDir = new File(MYLOG_PATH_SDCARD_DIR);
	 //File sdDir = Environment.getExternalStorageDirectory();	 
	 File file=null;
	 if(!sdDir.exists())		 
	 {
		 return;
	 }
	 String[] list = sdDir.list();
	 for(int i=0;i<list.length;i++)
	 {
		 //android.util.Log.v("LF_Debug", list[i]);
		 if(list[i].contains(FILE_NAME))
		 {        	         	 
		     file = new File(sdDir, list[i]);
		     if (file.exists()) 
		     {
		    	 dbg_mPrintf("LF_Debug", "删除:"+list[i]);
		         file.delete();
		     }
	     }
	 }
  }
  
  public static void dbg_delallfile_exceptioncurday() 
  {
	 // TODO Auto-generated method stub
	 File sdDir = new File(MYLOG_PATH_SDCARD_DIR);
	 //File sdDir = Environment.getExternalStorageDirectory();
	 String needsaveFiel = logfile.format(getDateCurrent());
	 File file=null;
	 if(!sdDir.exists())		 
	 {
		 return;
	 }
	 String[] list = sdDir.list();
	 for(int i=0;i<list.length;i++)
	 {
		 //android.util.Log.v("LF_Debug", list[i]);
		 if(list[i].contains(FILE_NAME))
		 {        	 
			 if(list[i].contains(needsaveFiel + FILE_NAME))
			 {
				 dbg_mPrintf("LF_Debug", "当天log不删除:"+needsaveFiel+FILE_NAME);
				 continue;
			 }
			 file = new File(sdDir, list[i]);
			 if (file.exists()) 
			 {
				 dbg_mPrintf("LF_Debug", "删除:"+list[i]);
	             file.delete();
	         }
	      }
	  }
  }
  
  public static void dbg_ftpserver(String ip, Integer port, Context context)
  {
	  
  }
	  
  public static void dbg_ftpserver(String ip, Integer port)
  {
	 
  }
  
  public static void dbg_ftpauth(String username, String password)
  {
	  
  }
  
  public static void dbg_setftppath(String path){
	  ftppath = path;
  }
  
  public static void dbg_setftpimei(String imei)
  {
	  ftpimei = imei;
  }
  
  public static void dbg_setftpupload(String upload)
  {
	  
  }
  
  
 
}
